//简单工厂模式
//利用虚类，写一个公共的接口，然后利用一个工厂类，生产不同的产品，调用不同的接口
//从而实现可扩展、低耦合的代码
#include <iostream>
#include <string>
#include <memory>

class AbstracCalc
{
public:
    using ptr = std::shared_ptr<AbstracCalc>;
    virtual int getResult(int num1, int num2)
    {
        return 0;
    }
};

class Add : public AbstracCalc
{
public:
    int getResult(int num1, int num2) override
    {
        return num1 + num2;
    }
};

class Minus : public AbstracCalc
{
public:
    int getResult(int num1, int num2) override
    {
        return num1 - num2;
    }
};

class Multi : public AbstracCalc
{
public:
    int getResult(int num1, int num2) override
    {
        return num1 * num2;
    }
};

class Divide : public AbstracCalc
{
public:
    int getResult(int num1, int num2) override
    {
        return num1 / num2;
    }
};

class Factory
{
public:
    using ptr = std::shared_ptr<Factory>;
    Factory() = delete;
    Factory(char symbol)
    {
        getOper(symbol);
    }
    void getOper(char symbol)
    {
        //记住make_shared的使用方法
        switch (symbol)
        {
        case '+':
            calc = std::make_shared<Add>();
            break;
        case '-':
            calc = std::make_shared<Minus>();
            break;
        case '*':
            calc = std::make_shared<Multi>();
            break;
        case '/':
            calc = std::make_shared<Divide>();
            break;
        default:
            break;
        }
    }
    int getResult(int num1, int num2)
    {
        return calc->getResult(num1, num2);
    }

private:
    AbstracCalc::ptr calc;
};

int main(int argc, char **argv)
{
    int a = 10;
    int b = 20;
    Factory::ptr factory(new Factory('*'));
    std::cout << "a*b=" << factory->getResult(a, b) << std::endl;
    factory->getOper('+');
    std::cout << "a+b=" << factory->getResult(a, b) << std::endl;
    return 0;
}